package com.foreveross.proxyip.infra.memcached;

import java.net.InetSocketAddress;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeoutException;

import net.rubyeye.xmemcached.MemcachedClient;
import net.rubyeye.xmemcached.exception.MemcachedException;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;

import com.foreveross.proxyip.infra.exception.CacheNotSupportException;

/**
 * memcache 操作管理类
 * @author lyq
 */
//@Service
public class MemcachedManager {
	
	
	@Autowired
	@Qualifier("memcachedClient")
	protected MemcachedClient client ;
	
	
	protected static final String DEFALUT_CACHE_KEY_PRE = "proxyip_server_";

	/**
	 * 默认缓存1个月
	 * 缓存对象（需要序列化）
	 * @param key
	 * @param value
	 * @return
	 * @throws Exception
	 */
	public boolean put(String key, Object value) throws CacheNotSupportException {
		try {
			return client.set(new StringBuffer(DEFALUT_CACHE_KEY_PRE).append(key).toString(), 0, value);
		} catch (Exception e) {
			throw new CacheNotSupportException("添加缓存错误：", e);
		}
	}
	
	/*public boolean contains(String key) throws CacheNotSupportException{
		try {
			return client.get(new StringBuffer(DEFALUT_CACHE_KEY_PRE).append(key).toString());
		} catch (Exception e) {
			throw new CacheNotSupportException("不存在:"+key+"，或者已过期", e);
		} 
	}*/

	/**
	 * 缓存数据
	 * 
	 * @param key
	 * @param value
	 *            缓存对象（需要序列化）
	 * @param second
	 *            缓存多少秒
	 * @return
	 * @throws Exception
	 */
	public boolean put(String key, Object value, int second) throws Exception {
		try {
			return client.set(new StringBuffer(DEFALUT_CACHE_KEY_PRE).append(key).toString(), second, value);
		} catch (Exception e) {
			throw new CacheNotSupportException("添加缓存错误：", e);
		}
	}
	

	/**
	 * 根据Key取缓存
	 * 
	 * @param key
	 * @return
	 * @throws Exception
	 */
	public Object get(String key) throws CacheNotSupportException {
		try {
			return client.get(new StringBuffer(DEFALUT_CACHE_KEY_PRE).append(key).toString());
		} catch (Exception e) {
			throw new CacheNotSupportException("取缓存错误：", e);
		}
	}

	/**
	 * 根据Keys批量取缓存
	 * 
	 * @param key
	 * @return
	 * @throws Exception
	 */
	public Map<String, Object> gets(List<String> keys) throws Exception {
		if (keys == null) {
			return null;
		}
		try {
			return client.get(keys);
		} catch (Exception e) {
			throw new CacheNotSupportException("取缓存错误：", e);
		}
	}

	/**
	 * 更新缓存，缓存时间默认一个月
	 * 
	 * @param key
	 * @param value
	 *            缓存对象（需要序列化）
	 * @return
	 * @throws Exception
	 */
	public boolean update(String key, Object value) throws CacheNotSupportException {
		try {
			return client.replace(DEFALUT_CACHE_KEY_PRE+key, 0, value);
		} catch (Exception e) {
			throw new CacheNotSupportException("更新缓存错误：", e);
		}
	}

	/**
	 * 更新缓存
	 * 
	 * @param key
	 * @param value
	 *            缓存对象（需要序列化）
	 * @param second
	 *            缓存多少秒
	 * @return
	 * @throws Exception
	 */
	public boolean update(String key, Object value, int second)
			throws CacheNotSupportException {
		try {
			return client.replace(DEFALUT_CACHE_KEY_PRE+key, second, value);
		} catch (Exception e) {
			throw new CacheNotSupportException("更新缓存错误：", e);
		}
	}

	/**
	 * 删除缓存
	 * 
	 * @param key
	 * @return
	 * @throws Exception
	 */
	public boolean delete(String key) throws Exception {
		try {
			return client.delete(DEFALUT_CACHE_KEY_PRE+key);
		} catch (Exception e) {
			throw new CacheNotSupportException("删除key=" + key + "的缓存错误：", e);
		}
	}

	/**
	 * 查询某个实例的元素个数
	 * 
	 * @param addr
	 * @return count
	 * @throws Exception
	 */
	public long getItemCount(InetSocketAddress addr) throws Exception {
		long count = 0;
		try {
			Map<InetSocketAddress, Map<String, String>> cacheMap = client
					.getStats();
			Map<String, String> statsMap = cacheMap.get(addr);
			count = Long.parseLong(statsMap.get("curr_items"));
		} catch (Exception e) {
			throw new CacheNotSupportException("获取缓存元素数量错误,addr:" + addr.toString());
		}
		return count;
	}

	/**
	 * 查询数据所在实例的元素总数
	 * 
	 * @return count
	 * @throws Exception
	 */
	public int getItemCount() throws Exception {
		int count = 0;
		try {
			Collection<InetSocketAddress> addrList = this.client.getAvailableServers();
			for (InetSocketAddress addr : addrList) {
				count += getItemCount(addr);
			}
		} catch (Exception e) {
			throw new CacheNotSupportException("获取缓存元素数量错误!");
		}
		return count;
	}

	/**
	 * 使所有缓存内容失效
	 * 
	 * @throws MemcachedException
	 * @throws InterruptedException
	 * @throws TimeoutException
	 */
	public void flushAll() throws Exception {
		client.flushAll();
	}
}